From 5fe2148740c059032b10d50e0402b07580cbd380 Mon Sep 17 00:00:00 2001 From: oliskoli Date: Sat, 6 Sep 2008 22:27:04 +0000 Subject: [PATCH] mapasia: Add write support. --- Makefile.in | 2 +- mapasia.c | 235 +++++++++++++++++++++++++++++++++++++++------------- 2 files changed, 178 insertions(+), 59 deletions(-) diff --git a/Makefile.in b/Makefile.in index 1e884f159..26a798b32 100644 --- a/Makefile.in +++ b/Makefile.in @@ -757,7 +757,7 @@ tpo.o: tpo.c defs.h config.h queue.h gbtypes.h zlib/zlib.h zlib/zconf.h \ jeeps/gpscom.h jeeps/gpsfmt.h jeeps/gpsmath.h jeeps/gpsmem.h \ jeeps/gpsrqst.h jeeps/gpsinput.h jeeps/gpsproj.h mapasia.o: mapasia.c defs.h config.h queue.h gbtypes.h zlib/zlib.h \ - zlib/zconf.h gbfile.h cet.h cet_util.h inifile.h csv_util.h + zlib/zconf.h gbfile.h cet.h cet_util.h inifile.h csv_util.h session.h trackfilter.o: trackfilter.c defs.h config.h queue.h gbtypes.h \ zlib/zlib.h zlib/zconf.h gbfile.h cet.h cet_util.h inifile.h \ filterdefs.h strptime.h grtcirc.h diff --git a/mapasia.c b/mapasia.c index e42d5fba6..d85bdef22 100644 --- a/mapasia.c +++ b/mapasia.c @@ -25,11 +25,13 @@ #include #include #include "defs.h" -#include "jeeps/gpsmath.h" +#include "session.h" -#define MYNAME "tr7" +#define MYNAME "mapasia" -#define TR7_TRACK_MAGIC 0x223eadb +#define TR7_TRACK_MAGIC 0x223EADB + +#define TR7_S_SIZE 32 #define TR7_S_YEAR 0 #define TR7_S_MONTH 2 @@ -44,12 +46,16 @@ #define TR7_S_VALID 28 #define TR7_S_FIX 29 +static gbfile *fin, *fout; +static const waypoint *wpt_tmp; +static const route_head *trk_tmp; +static int course_tmp, speed_tmp; + static arglist_t tr7_args[] = { ARG_TERMINATOR }; -static gbfile *fin; /******************************************************************************* * %%% global callbacks called by gpsbabel main process %%% * @@ -80,75 +86,188 @@ tr7_read(void) } while (! gbfeof(fin)) { - unsigned char buff[32]; + unsigned char buff[TR7_S_SIZE]; + double lat, lon; + struct tm tm; + waypoint *wpt; + gbfread(buff, 1, sizeof(buff), fin); - if (buff[0] == 0xD8) { - double lat, lon; - struct tm tm; - waypoint *wpt; - - memset(&tm, 0, sizeof(tm)); - - lat = (double)le_read32(&buff[TR7_S_LAT]) / 1000000.0; - lon = (double)le_read32(&buff[TR7_S_LON]) / 1000000.0; - if ((fabs(lat) > 90) || (fabs(lon) > 180)) { - trk = NULL; - continue; - } - - tm.tm_year = le_read16(&buff[TR7_S_YEAR]) - 1900; - tm.tm_mon = buff[TR7_S_MONTH] - 1; - tm.tm_mday = buff[TR7_S_DAY]; - - tm.tm_hour = buff[TR7_S_HOUR]; - tm.tm_min = buff[TR7_S_MIN]; - tm.tm_sec = buff[TR7_S_SEC]; - - wpt = waypt_new(); - - wpt->latitude = lat; - wpt->longitude = lon; + + memset(&tm, 0, sizeof(tm)); + + lat = (double)le_read32(&buff[TR7_S_LAT]) / 1000000.0; + lon = (double)le_read32(&buff[TR7_S_LON]) / 1000000.0; + + if ((fabs(lat) > 90) || (fabs(lon) > 180)) { /* that really happens */ + trk = NULL; + continue; + } + + tm.tm_year = le_read16(&buff[TR7_S_YEAR]); + tm.tm_mon = buff[TR7_S_MONTH]; + tm.tm_mday = buff[TR7_S_DAY]; + tm.tm_hour = buff[TR7_S_HOUR]; + tm.tm_min = buff[TR7_S_MIN]; + tm.tm_sec = buff[TR7_S_SEC]; + + wpt = waypt_new(); + + wpt->latitude = lat; + wpt->longitude = lon; + + /* create only valid timestamps */ + if (tm.tm_mday && (tm.tm_mday <= 31) && tm.tm_mon && (tm.tm_mon <= 12) && (tm.tm_year > 1970)) { + tm.tm_year -= 1900; + tm.tm_mon -= 1; wpt->creation_time = mkgmtime(&tm); - WAYPT_SET(wpt, course, 360 - le_read16(&buff[TR7_S_COURSE])); - WAYPT_SET(wpt, speed, (double)le_read16(&buff[TR7_S_SPEED]) / 3.6); -#if 0 - /* unsure items */ - wpt->fix = buff[TR7_S_FIX]; - if (buff[TR7_S_VALID] != 'A') { - waypt_free(wpt); - continue; - } + } + + WAYPT_SET(wpt, course, 360 - le_read16(&buff[TR7_S_COURSE])); + WAYPT_SET(wpt, speed, KPH_TO_MPS(le_read16(&buff[TR7_S_SPEED]))); + +#if 0 /* unsure, not validated items */ + wpt->fix = buff[TR7_S_FIX]; + if (buff[TR7_S_VALID] != 'A') { + waypt_free(wpt); + continue; + } +#endif + if (waypt_speed(prev, wpt) > 9999.9) { /* filter out some bad trackpoints */ + waypt_free(wpt); + continue; + } + + if (prev) { /* other track or bad timestamp */ + if (wpt->creation_time && (prev->creation_time > wpt->creation_time)) trk = NULL; + else if (waypt_distance(prev, wpt) > 9999.9) trk = NULL; + } + + if (! trk) { + trk = route_head_alloc(); + track_add_head(trk); + } + track_add_wpt(trk, wpt); + prev = wpt; + } +} + +/**************************************************************************/ + +static void +tr7_disp_track_head_cb(const route_head *trk) +{ + wpt_tmp = NULL; +} + +static void +tr7_disp_waypt_cb(const waypoint *wpt) +{ + unsigned char buff[TR7_S_SIZE]; + struct tm tm; + double speed, course; + + memset(buff, 0, sizeof(buff)); + + le_write32(&buff[TR7_S_LON], (int)(wpt->longitude * 1000000.0)); + le_write32(&buff[TR7_S_LAT], (int)(wpt->latitude * 1000000.0)); + + if WAYPT_HAS(wpt, course) course = wpt->course; + else if (wpt_tmp != NULL) course = waypt_course(wpt_tmp, wpt); + else course = -1; + if (course >= 0) le_write16(&buff[TR7_S_COURSE], (int)(360 - course)); + + if (wpt->creation_time) { + tm = *gmtime(&wpt->creation_time); + + le_write16(&buff[TR7_S_YEAR], tm.tm_year + 1900); + buff[TR7_S_MONTH] = tm.tm_mon + 1; + buff[TR7_S_DAY] = tm.tm_mday; + buff[TR7_S_HOUR] = tm.tm_hour; + buff[TR7_S_MIN] = tm.tm_min; + buff[TR7_S_SEC] = tm.tm_sec; + + if WAYPT_HAS(wpt, speed) speed = wpt->speed; + else if (wpt_tmp != NULL) speed = waypt_speed(wpt_tmp, wpt); + else speed = -1; + if (speed >= 0) le_write16(&buff[TR7_S_SPEED], (int)MPS_TO_KPH(speed)); + } + buff[TR7_S_VALID] = 'A'; /* meaning unknown */ + +#if 0 /* not validated */ + if (wpt->fix != fix_unknown) buff[TR7_S_FIX] = wpt->fix; #endif - if (waypt_speed(prev, wpt) > 9999.9) { - waypt_free(wpt); - continue; - } - - if (! trk) { - trk = route_head_alloc(); - track_add_head(trk); - } - track_add_wpt(trk, wpt); - prev = wpt; + gbfwrite(buff, 1, sizeof(buff), fout); + + wpt_tmp = wpt; +} + +static void +tr7_wr_init(const char *fname) +{ + fout = gbfopen_le(fname, "wb", MYNAME); + gbfputint32(TR7_TRACK_MAGIC, fout); +} + +static void +tr7_check_after_read_head_cb(const route_head *trk) +{ + trk_tmp = trk; + course_tmp = 0; + speed_tmp = 0; +} + +static void +tr7_check_after_read_wpt_cb(const waypoint *wpt) +{ + if (wpt->speed != 0) speed_tmp = 1; + if (wpt->course != 360.0) course_tmp = 1; +} + +static void +tr7_check_after_read_trailer_cb(const route_head *trk) +{ + queue *elem, *tmp; + QUEUE_FOR_EACH((queue *)&trk->waypoint_list, elem, tmp) { + waypoint *wpt = (waypoint *)elem; + if (speed_tmp == 0) WAYPT_UNSET(wpt, speed); + if (course_tmp == 0) { + WAYPT_UNSET(wpt, course); + wpt->course = 0; } } } +static void +tr7_wr_deinit(void) +{ + track_disp_session(curr_session(), + tr7_check_after_read_head_cb, + tr7_check_after_read_trailer_cb, + tr7_check_after_read_wpt_cb); + gbfclose(fout); +} + +static void +tr7_write(void) +{ + track_disp_all(tr7_disp_track_head_cb, NULL, tr7_disp_waypt_cb); +} + /**************************************************************************/ -ff_vecs_t mapasia_tr7_vecs = { /* currently we can only read tracks */ +ff_vecs_t mapasia_tr7_vecs = { /* we can read and write tracks */ ff_type_file, { - ff_cap_none /* waypoints */, - ff_cap_read /* tracks */, - ff_cap_none /* routes */ + ff_cap_none /* waypoints */, + ff_cap_read | ff_cap_write /* tracks */, + ff_cap_none /* routes */ }, tr7_rd_init, - NULL, + tr7_wr_init, tr7_rd_deinit, - NULL, + tr7_wr_deinit, tr7_read, - NULL, + tr7_write, NULL, tr7_args, CET_CHARSET_UTF8, 1 /* FIXED - CET-REVIEW - */ -- 2.30.2